﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Windows.Media.Effects;
using UI.Model;
using Microsoft.M;
using UI.Presenters;
using Microsoft.Scripting.Hosting;
using IronPython.Hosting;
using Microsoft.Win32;

namespace UI
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public static RoutedCommand Simulate = new RoutedCommand("Simulate", typeof(MainWindow));
        public static RoutedCommand ImportExport = new RoutedCommand("ImportExport", typeof(MainWindow));
        private FilterDocManager _documentManager;
        //private FilterRepository _coeffRepos;
        private ApplicationPresenter P;

        public MainWindow()
        {
            InitializeComponent();
            CommandBinding SimulateCommandBinding = new CommandBinding(Simulate, Simulation_Executed);
            this.CommandBindings.Add(SimulateCommandBinding);
            toolbar.Sim.Command = Simulate;
            CommandBinding ImportExportCommandBinding = new CommandBinding(ImportExport, ImportExport_Executed);
            this.CommandBindings.Add(ImportExportCommandBinding);
            toolbar.ImpExp.Command = ImportExport;
            _documentManager = new FilterDocManager(textInBox);
/*            if (_documentManager.OpenDocument())
                status.Text = "“Document loaded.”";*/
            P = new ApplicationPresenter(this, new FilterRepository());
            DataContext = P;
//            Simulate = new RoutedCommand("Simulate", typeof(MainWindow));
        }
        //ChartTab myTabChart;

        private void About_Click(object sender, RoutedEventArgs e)
        {
            var blur = new BlurEffect();
            var current = this.Background;
            blur.Radius = 5;
            this.Background = new SolidColorBrush(Colors.DarkGray);
            this.Effect = blur; 
            MessageBox.Show(
                "“Digital Filter Simulation Integrated Development Environment”",
                "“About”"
            );
            this.Effect = null;
            this.Background = current;
        }

        private void NewDocument(object sender, ExecutedRoutedEventArgs e)
        {
            _documentManager.NewDocument();
            status.Text = "“New Document”";
        }
        private void OpenDocument(object sender, ExecutedRoutedEventArgs e)
        {
            if (_documentManager.OpenDocument())
            status.Text = "“Document loaded.”";
        }
        private void SaveDocument_CanExecute(object sender,CanExecuteRoutedEventArgs e)
        {
            e.CanExecute = _documentManager.CanSaveDocument();
        }
        private void SaveDocument(object sender, ExecutedRoutedEventArgs e)
        {
            if (_documentManager.SaveDocument())
            status.Text = "“Document saved.”";
        }
        private void SaveDocumentAs(object sender,ExecutedRoutedEventArgs e)
        {
            if (_documentManager.SaveDocumentAs())
            status.Text = "“Document saved.”";
        }
        private void ApplicationClose(object sender,ExecutedRoutedEventArgs e)
        {
            Close();
        }
        public void AddTab<T>(PresenterBase<T> presenter)
        {
            TabItem newTab = null;
            for (int i = 0; i < tabs.Items.Count; i++)
            {
                TabItem existingTab = (TabItem)tabs.Items[i];
                if (existingTab.DataContext.Equals(presenter))
                {
                    tabs.Items.Remove(existingTab);
                    newTab = existingTab;
                    break;
                }
            }
            if (newTab == null)
            {
                newTab = new TabItem();
                Binding headerBinding = new Binding(presenter.TabHeaderPath);
                BindingOperations.SetBinding(
                newTab,
                TabItem.HeaderProperty,
                headerBinding
                );
                newTab.DataContext = presenter;
                newTab.Content = presenter.View;
            }
            tabs.Items.Insert(0, newTab);
            newTab.Focus();
        }
        public void RemoveTab<T>(PresenterBase<T> presenter)
        {
            for (int i = 0; i < tabs.Items.Count; i++)
            {
                TabItem item = (TabItem)tabs.Items[i];
//                if (item.DataContext.Equals(presenter))
//                {
                    tabs.Items.Remove(item);
//                    break;
//                }
            }
        }

        private void FeaturesToolbar_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            if (toolbar.IsSynchronizing) return;
            ComboBox source = e.OriginalSource as ComboBox;
            if (source == null) return;
            switch (source.Name)
            {
            case "fonts":
                _documentManager.ApplyToSelection(TextBlock.FontFamilyProperty, source.SelectedItem);
                break;
            case "fontSize":
                _documentManager.ApplyToSelection(TextBlock.FontSizeProperty, source.SelectedItem);
                break;
            }
            textInBox.Focus();
        }

        private void textIn_SelectionChanged(object sender, RoutedEventArgs e)
        {
            //update the tool bar
            toolbar.SynchronizeWith(textInBox.Selection);
        }

        private void Simulation_Executed(object sender, ExecutedRoutedEventArgs e)
        {
            RemoveTab(P);
            P.UpdateSimCharts(textInBox);
            
            /*
            _coeffRepos = new FilterRepository();
            _coeffRepos.Parse(textInBox);
            
            TextRange range = new TextRange(
                textInBox.Document.ContentStart,
        textInBox.Document.ContentEnd
        );
            var language = Language.LoadFromCurrentAssembly("UI", "Filteration");
            dynamic result = language.ParseString(range.Text);
            //result.
            Console.Write(result); Console.Read();
            range.Text = Convert.ToString(result);
            
            myTabChart= new ChartTab();
            IOLayout.Children.Add(myTabChart);
            myTabChart.SetValue(Grid.ColumnProperty, 2);
            myTabChart.DataContext = new KeyValuePair<string, int>[] {
                new KeyValuePair<string, int>("Silverlight", 9), 
                new KeyValuePair<string, int>(".NET 3.5", 2), 
                new KeyValuePair<string, int>("ASP", 4), 
                new KeyValuePair<string, int>("AJAX", 8), 
                new KeyValuePair<string, int>("VC++", 1),
                new KeyValuePair<string, int>("C#", 3),
                new KeyValuePair<string, int>("SQL Server", 10) 
            };*/
        }

        private void ImportExport_Executed(object sender, ExecutedRoutedEventArgs e)
        {
            // Set the current directory to the IronPython libraries.
/*            System.IO.Directory.SetCurrentDirectory(
               Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles) +
               @" (x86)\IronPython 2.6 for .NET 4.0 RC\Lib");
            */
            // Create an instance of the random.py IronPython library.
            Console.WriteLine("Loading random.py");
            ScriptRuntime py = Python.CreateRuntime();
            OpenFileDialog dlg = new OpenFileDialog();
            dlg.Filter = "IronPython Script|*.py";
            if (dlg.ShowDialog() == true)
            {
                dynamic random = py.UseFile(dlg.FileName);

                Console.WriteLine(dlg.FileName + " loaded.");
                if (random.hasExport())
                {
                    FilterRepository _coeffRepos = new FilterRepository();
                    _coeffRepos.Parse(textInBox);
                    random.export(_coeffRepos.giveTaps());
                }
                else
                {
                    List<double> taps = random.imp();
                    TextRange range = new TextRange(
                            textInBox.Document.ContentStart,
                            textInBox.Document.ContentEnd
                        );
                    range.Text = "";
                    for (int i = 0; i < taps.Count; i++)
                    {
                        textInBox.AppendText(taps[i].ToString());
                        textInBox.AppendText(" ");
                    }
                }
            }
/*            // Initialize an enumerable set of integers.
            int[] items = Enumerable.Range(1, 7).ToArray();
            foreach (int item in items)
            {
                Console.WriteLine(item);
            }
            Console.WriteLine("-------------------");
            // Randomly shuffle the array of integers by using IronPython.
            for (int i = 0; i < 5; i++)
            {
                random.shuffle(items);
                foreach (int item in items)
                {
                    Console.WriteLine(item);
                }
                Console.WriteLine("-------------------");
            }
            Console.ReadKey();*/
        }

        private void FileT_Click(object sender, RoutedEventArgs e)
        {
            if (toolbar.FileT.IsVisible)
                toolbar.FileT.Visibility = Visibility.Collapsed;
            else
                toolbar.FileT.Visibility = Visibility.Visible;
        }

        private void Editing_Click(object sender, RoutedEventArgs e)
        {
            if (toolbar.EditingT.IsVisible)
                toolbar.EditingT.Visibility = Visibility.Collapsed;
            else
                toolbar.EditingT.Visibility = Visibility.Visible;
        }

        private void Formatting_Click(object sender, RoutedEventArgs e)
        {
            if (toolbar.FormatT.IsVisible)
                toolbar.FormatT.Visibility = Visibility.Collapsed;
            else
                toolbar.FormatT.Visibility = Visibility.Visible;
        }
    }
}
